/*
给你一个字符串 path ，表示指向某一文件或目录的 Unix 风格 绝对路径 （以 '/' 开头），请你将其转化为更加简洁的规范路径。

在 Unix 风格的文件系统中，一个点（.）表示当前目录本身；此外，两个点 （..） 表示将目录切换到上一级（指向父目录）；两者都可以是复杂相对路径的组成部分。任意多个连续的斜杠（即，'//'）都被视为单个斜杠 '/' 。 对于此问题，任何其他格式的点（例如，'...'）均被视为文件/目录名称。

请注意，返回的 规范路径 必须遵循下述格式：

始终以斜杠 '/' 开头。
两个目录名之间必须只有一个斜杠 '/' 。
最后一个目录名（如果存在）不能 以 '/' 结尾。
此外，路径仅包含从根目录到目标文件或目录的路径上的目录（即，不含 '.' 或 '..'）。
返回简化后得到的 规范路径 。

 

示例 1：

输入：path = "/home/"
输出："/home"
解释：注意，最后一个目录名后面没有斜杠。 
示例 2：

输入：path = "/../"
输出："/"
解释：从根目录向上一级是不可行的，因为根目录是你可以到达的最高级。
示例 3：

输入：path = "/home//foo/"
输出："/home/foo"
解释：在规范路径中，多个连续斜杠需要用一个斜杠替换。
示例 4：

输入：path = "/a/./b/../../c/"
输出："/c"
 

提示：

1 <= path.length <= 3000
path 由英文字母，数字，'.'，'/' 或 '_' 组成。
path 是一个有效的 Unix 风格绝对路径。

来源：力扣（LeetCode）
链接：https://leetcode-cn.com/problems/simplify-path
著作权归领扣网络所有。商业转载请联系官方授权，非商业转载请注明出处。
*/

#include <string>
#include <sstream>
#include <vector>

using namespace std;

// C++中也有专门处理字符串的机制，我们可以使用stringstream来分隔字符串，然后对每一段分别处理
class Solution {
public:
    string simplifyPath(string path) {
        string res;
        string t;
        stringstream ss(path);
        vector<string> v;
        while (getline(ss, t, '/')) {
            if (t == "" || t == ".") {
                continue;
            }
            if (t == ".." && !v.empty()) {
                v.pop_back();
            } else if (t != "..") {
                v.push_back(t);
            }
        }
        for (string s : v) {
            res += "/" + s;
        }
        return res.empty() ? "/" : res;
    }
};

class Solution {
public:
    string simplifyPath(string path) {
        auto split = [](const string& s, char delim) -> vector<string> {
            vector<string> res;
            string cur;
            for (const char& c : s) {
                if (c == delim) {
                    res.push_back(move(cur));
                    cur.clear();
                } else {
                    cur += c;
                }
            }
            res.push_back(move(cur));
            return res;
        };
        vector<string> names = split(path, '/');
        vector<string> deque;
        for (string& name : names) {
            if (name == "" || name == ".") {
                continue;
            } else if (name == "..") {
                if (!deque.empty()) {
                    deque.pop_back();
                }
            } else {
                deque.push_back(move(name));
            }
        }
        string res;
        for (string& name : deque) {
            res += "/" + move(name);
        }
        return res.empty() ? "/" : res;
    }
};
